One of the features common to modern object oriented frameworks is the concept of metadata. Metadata provides additional information about a file, class, or member of another component of a class hierarchy, for example. The Microsoft Common Language Runtime (CLR) is the heart of the MICROSOFT .NET framework, and provides the execution environment for .NET code. The CLR uses metadata for diverse needs that range from tool support to marshaling characteristics. The CLR supports the addition of these attributes at compile time through the use of a special syntax. For example, to indicate that a member variable should be stored in thread local storage, one may place an attribute on the variable:
[ThreadStatic]private string perThreadString;
In this example, tying the attribute into the source code is proper, because the source code breaks if the attribute is not present. Sometimes this is not desirable, however. Consider:
[Editor(typeof(ColorEditor))]public class Color { }This attribute specifies the type of user interface to instantiate if a user is to edit an instance of a color object. It provides an extensibility point so third parties can provide their own data types that can be seamlessly edited in applications. However, many color editors exist. Therefore, choosing a color editor at compile time is incorrect. But, if there is no way to provide for a class to specify an editor at compile time, third parties would be prevented from adding new types to the system, as they could not be edited until applications are written to support them.
CLR metadata contains more than attributes as described above. Late binding mechanisms such as reflection discover types, methods, and other members through metadata. Code running in the CLR uses metadata to link members and classes of different modules. Therefore, metadata defines the contract of the application programming interface (API) of a class library.
Sometimes it may be useful to modify this contract. For example, the .NET compact framework is a strict subset of the .NET framework that is available on the desktop. The compact framework cannot be instantiated on a desktop personal computer, however. Because it is a strict subset of the desktop framework, whenever an instance of a compact framework object needs to be instantiated, applications will instead create an instance of the corresponding desktop object. This poses a problem when late bound technologies such as reflection are used to inspect the created object. Consider a class called Font that represents a system font. Reflecting on the desktop object will expose properties and lists of available fonts that are not available on the compact framework's Font class. This problem is not limited to the compact framework.
Additionally, versioning an API is another way this problem is introduced. Consider an application that allows the production of HTML files. The file may be written to correspond to HTML 4.0 or 3.2. Applications traditionally hardwire the API schema for each version. This technique breaks down when the schema is not known ahead of time, as it is for scenarios where third party extensibility is involved.